package com.ouyunc.oauth2.exception.handler;


import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.ouyunc.common.constant.enums.ResponseCodeEnum;
import com.ouyunc.oauth2.exception.IOAuth2Exception;
import com.ouyunc.common.base.ResponseResult;
import com.ouyunc.web.exception.handler.GlobalExceptionHandler;
import feign.FeignException;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpStatus;
import org.springframework.security.oauth2.common.exceptions.OAuth2Exception;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.bind.annotation.RestControllerAdvice;

import javax.servlet.http.HttpServletResponse;


/**
 * @Author fangzhenxun
 * @Description 全局异常处理器
 * PropertyResourceBundle
 * @Date 2020/4/23 14:49
 **/
@RestControllerAdvice
public class Auth2GlobalExceptionHandler extends GlobalExceptionHandler {
    private static Logger log = LoggerFactory.getLogger(Auth2GlobalExceptionHandler.class);


    /**
     * @Author fangzhenxun
     * @Description 捕获oauth2 异常
     * @param ex
     * @return com.ouyunc.common.base.ResponseResult
     */
    @ExceptionHandler(value = OAuth2Exception.class)
    @ResponseStatus(HttpStatus.UNAUTHORIZED)
    public ResponseResult oAuth2Exception(OAuth2Exception ex) {
        log.error("OAuth2Exception 异常: {}", ex.getMessage());
        return ResponseResult.error(ResponseCodeEnum.UNAUTHORIZED, ex.getMessage());
    }


    /**
     * @Author fangzhenxun
     * @Description 捕获oauth2 异常
     * @param ex
     * @return com.ouyunc.common.base.ResponseResult
     */
    @ExceptionHandler(value = IOAuth2Exception.class)
    @ResponseStatus(HttpStatus.BAD_REQUEST)
    public ResponseResult iOAuth2Exception(IOAuth2Exception ex) {
        log.error("OAuth2Exception 异常: {}", ex.getMessage());
        return ResponseResult.error(ResponseCodeEnum.BAD_REQUEST, ex.getMessage());
    }

    /**
     * @Author fangzhenxun
     * @Description 捕获feign异常,如果使用feign 调用会被feign 吃掉然后抛出feign异常；
     * 注意这里区分几种，1-页面级别，2-restful级别 @todo 需要手动设置状态吗
     * @param feignException
     * @return com.ouyunc.common.base.ResponseResult
     */
    @ExceptionHandler(value = FeignException.class)
    public ResponseResult feignException(FeignException feignException, HttpServletResponse response) {
        log.error("oauth2相关feign 异常: {}", feignException.getMessage());
        JSONObject jsonObject = JSON.parseObject(feignException.contentUTF8());
        Integer status = jsonObject.getInteger("status");
        Integer code = jsonObject.getInteger("code");
        String errorDescription = jsonObject.getString("error_description");

        // 自定义的异常
        if (code != null) {
            response.setStatus(code);
            return jsonObject.toJavaObject(ResponseResult.class);
        }else if (status != null) {
            // 框架抛出的异常类型 1
            response.setStatus(status);
            return ResponseResult.common(status, jsonObject.getString("message"), null, true);
        }else if (StringUtils.isNotBlank(errorDescription)){
            // 框架抛出的异常类型 2
            response.setStatus(ResponseCodeEnum.UNAUTHORIZED.code());
            return ResponseResult.error(ResponseCodeEnum.UNAUTHORIZED, errorDescription);
        } else {
            response.setStatus(ResponseCodeEnum.INTERNAL_SERVER_ERROR.code());
            return ResponseResult.error("认证服务未知错误！");
        }


    }






}
